/*
 * wk_vector.c
 *
 *  Created on: 2012-3-8
 *      Author: tianmax
 */
#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>
#include "wk_vector.h"

/**
 * 分配内存
 */
static WPElement* wk_vector_alloc(size_t size){
	return (WPElement*)calloc(size,sizeof(WPElement));
}
/************************************************/

/**
 *
 * @param initsize:初始化大小
 * @param incrementsize:当向量溢出时每次增加的量
 */
extern WVector* wk_vector_init(wsize_t initsize,wsize_t incrementsize,wk_element_comp comp){

	/**
	 * 参数检查
	 */

	/**
	 * 建立WVector结构体
	 */
	WVector* vector=(WVector*)calloc(1,sizeof(WVector));
	if(vector==NULL){
		return NULL;
	}
	vector->data=wk_vector_alloc(initsize);
	if(vector->data==NULL){
		free(vector);
		vector=NULL;
		return NULL;
	}
	vector->initsize=initsize;
	vector->incrementsize=incrementsize;
	vector->size=initsize;
	vector->count=0;
	vector->current=vector->data;
	vector->comp=comp;

	return vector;
}
extern void wk_vector_destroy(WVector* vector){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return;
	}
	if(vector->data!=NULL){
		free(vector->data);
		vector->data=NULL;
	}
	free(vector);
	vector=NULL;
}
/************************************************/
/*设置比较器*/
extern int wk_vector_setComp(WVector* vector,wk_element_comp comp){
	if(!vector) return -1;
	vector->comp=comp;
	return 0;
}
/************************************************/
extern int wk_vector_initsize(WVector* vector){
	if(vector==NULL){
		return -1;
	}
	return vector->initsize;
}
extern int wk_vector_incrementsize(WVector* vector){
	if(vector==NULL){
		return -1;
	}
	return vector->incrementsize;
}
extern int wk_vector_size(WVector* vector){
	if(vector==NULL){
		return -1;
	}
	return vector->size;
}
extern int wk_vector_count(WVector* vector){
	if(vector==NULL){
		return -1;
	}
	return vector->count;
}
/**************************************************/
extern int wk_vector_sort(WVector* vector,wk_element_comp comp){

	return 0;
}
/*************************************************/
/**
 * 负责处理负数下标
 * -1表示最后一个元素，而不是指最后一个位置
 * 要操作的位置的元素必须存在
 */
extern int wk_vector_index(WVector* vector,int index){
	/*检查参数*/
	if(vector==NULL){
		return -1;
	}
	if(index>=0){
		return index;
	}else{
		//当下标为负数
		if((-index)>=vector->count){
			return 0;
		}else{
			return vector->count+index;
		}
	}
}

/**
 * 清除Vector中的所有内容，使其成为一个空Vector
 */
extern int wk_vector_clean(WVector* vector){
	/*参数检查*/
	if(vector==NULL){
		return -1;
	}
	int i;
	for(i=0;i<vector->size;i++){
		vector->data[i]=NULL;
	}
	vector->count=0;
	vector->current=vector->data;

	return 0;
}

/**
 * 返回当前的容量
 */
extern int wk_vector_capacity(WVector* vector){

	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}
	return vector->size-vector->count;
}

/*
*功能：增加指定数组的容量
*声明：有可能引起新内存申请，内存拷贝，从而改变指针具体指向
*参数：vector:要操作的数组指针地址 addsize:要增加的数量(这里用于选择)
*
*addsize:可以为负数
*/
/**
 * 增加vector的容量
 * 或者减少vector的容量
 *
 * 返回newsize
 */
extern int wk_vector_encapacity(WVector* vector,int addsize){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}
	int newsize=vector->size+addsize;
	if(newsize<0){
		return -1;
	}else if(newsize==0){
		free(vector->data);
		vector->size=0;
		vector->count=0;
		vector->current=NULL;
		vector->data=NULL;
	}else{
		WPElement* data=(WPElement*)realloc(vector->data,sizeof(WPElement)*newsize);
		if(data!=NULL){
			vector->data=data;
			vector->size=newsize;
		}
	}

	return newsize;
}

/**
 * 使容量和元素数量一样大
 *
 * 返回新容量或者错误码
 */
extern int wk_vector_trim2count(WVector* vector){

	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}

	int addsize=-(vector->size-vector->count);

	return wk_vector_encapacity(vector,addsize);
}

/**
 * 使vector具有指定大小的容量
 */
extern int wk_vector_resize(WVector* vector,wsize_t newsize){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}
	int addsize=newsize-vector->size;

	return wk_vector_encapacity(vector,addsize);
}

/**
 * 是否包含某元素
 */
extern int wk_vector_contains(WVector* vector,WPElement data){

	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}
	int i;
	for(i=0;i<wk_vector_count(vector);i++){
		//地址一样时，内容肯定一样
		if(vector->data==data){
			return 1;
		}
		if(vector->comp(vector->data[i],data)==0){
			return 1;
		}
	}

	return 0;
}

/**
 * 获取元素的下标
 *
 * -1表示没有找到
 */
extern int wk_vector_indexof(WVector* vector,WPElement data){

	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}

	int i;
	for(i=0;i<wk_vector_count(vector);i++){
		//地址一样时，内容肯定一样
		if(vector->data[i]==data){
			return i;
		}
		if(vector->comp(vector->data[i],data)==0){
			return 1;
		}
	}

	return -1;
}

/**
 * 返回-1表示没有找到
 */
extern int wk_vector_lastindexof(WVector* vector,WPElement data){

	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}

	int i;
	for(i=wk_vector_count(vector)-1;i>=0;i--){
		//地址一样时，内容肯定一样
		if(vector->data[i]==data){
			return i;
		}
		if(vector->comp(vector->data[i],data)==0){
			return 1;
		}
	}

	return -1;
}

/**
 * 是否为空
 */
extern int wk_vector_isempty(WVector* vector){

	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}

	return wk_vector_count(vector)>0?1:0;
}

/**
 * 是否满
 */
extern int wk_vector_isfull(WVector* vector){

	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}

	return wk_vector_count(vector)>=vector->size?1:0;
}
/*********************************/
extern int wk_vector_insert(WVector* vector,int index,WPElement data){

	/*参数检查*/
	if(vector==NULL){
		return -1;
	}

	//1.检查vector是否已满
	if(wk_vector_isfull(vector)==-1){
		//出错
		return -1;
	}else if(wk_vector_isfull(vector)==1){
		//已经满了
		//2.扩容
		if(wk_vector_encapacity(vector,vector->incrementsize)<0){
			return -1;
		}
		if(wk_vector_isfull(vector)!=0){
			return -1;
		}
	}
	/**处理负数下标**/
	/**
	 * 将数据元素计数器+1，便于处理负数下标
	 */
	vector->count++;
	index=wk_vector_index(vector,index);

	//假如index大于最后一个元素位置,那么将index置为最后一个元素后面的位置上
	if(index>=wk_vector_count(vector)){
		index=wk_vector_count(vector)-1;
	}
	//2.index位置后的数据往后移动
	int i=wk_vector_count(vector)-1;
	if(i<0){
		vector->count--;
		return -1;
	}else if(i==0){
		vector->data[0]=data;
	}else{
		for(;i>index;i--){
			vector->data[i]=vector->data[i-1];
		}
		vector->data[index]=data;
	}


	return 0;
}
/********************************/
extern int wk_vector_append(WVector* vector,WPElement data){

	/*参数检查*/
	if(vector==NULL){
		return -1;
	}
	//1.检查vector是否已满
	if(wk_vector_isfull(vector)==-1){
		//出错
		return -1;
	}else if(wk_vector_isfull(vector)==1){
		//已经满了
		//2.扩容
		if(wk_vector_encapacity(vector,vector->incrementsize)<0){
			return -1;
		}
		if(wk_vector_isfull(vector)!=0){
			return -1;
		}
	}
	//2.在vector末尾插入数据
	int count=wk_vector_count(vector);
	if(count<0){
		return -1;
	}
	vector->data[count]=data;
	vector->count++;

	return 0;
}
/*******************************/
extern int wk_vector_remove(WVector* vector,int index){

	/*参数检查*/
	if(vector==NULL){
		return -1;
	}
	int vector_len=wk_vector_count(vector);
	/**
	 * 处理index
	 */
	index=wk_vector_index(vector,index);
	/**
	 * 不可以等于，也不可以大于
	 * 也就是不允许当前要移除的元素不存在
	 */
	if(index>=vector_len){
		return -1;
	}
	//移动元素
	int i;
	for(i=index;i<vector_len-1;i++){
		vector->data[i]=vector->data[i+1];
	}
	vector->data[i]=NULL;
	vector->count--;

	return 0;
}
extern int wk_vector_removeFirst(WVector* vector){

	return wk_vector_remove(vector,0);
}
extern int wk_vector_removeLast(WVector* vector){

	return wk_vector_remove(vector,-1);
}
/********************************/
extern WPElement wk_vector_value(WVector* vector,int index){

	/*参数检查*/
	if(vector==NULL){
		return NULL;
	}
	int vector_len=wk_vector_count(vector);
	/**
	 * 处理index
	 */
	index=wk_vector_index(vector,index);
	/**
	 * 不可以等于，也不可以大于
	 * 也就是不允许当前要获取值的元素不存在
	 */
	if(index>=vector_len){
		return NULL;
	}

	return vector->data[index];
}
extern WPElement wk_vector_find(WVector* vector,WPElement data,
		wk_vector_iterator iterator,wk_element_iterate_do iterate_do){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return NULL;
	}
	WPElement retp=NULL;
	retp=(WPElement)iterator(vector,iterate_do,data);

	return retp;
}
/********************************/
/**
 * 获取当前链表指针指向位置的元素的值
 */
extern WPElement wk_vector_getcurrent(WVector* vector){

	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return NULL;
	}
	if(vector->current==NULL){
		return NULL;
	}else{
		return *vector->current;
	}

}
/********************************/
extern int wk_vector_replace(WVector* vector,int index,WPElement data){

	/*参数检查*/
	if(vector==NULL){
		return -1;
	}
	int vector_len=wk_vector_count(vector);
	/**
	 * 处理index
	 */
	index=wk_vector_index(vector,index);
	/**
	 * 不可以等于，也不可以大于
	 * 也就是不允许当前要获取值的元素不存在
	 */
	if(index>=vector_len){
		return -1;
	}
	vector->data[index]=data;

	return 0;
}
/******************************/
extern int wk_vector_push_front(WVector* vector,WPElement data){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}

	return wk_vector_insert(vector,0,data);
}
extern int wk_vector_push_back(WVector* vector,WPElement data){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}

	return wk_vector_append(vector,data);
}
/******************************/
extern void wk_vector_pop_front(WVector* vector){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return;
	}
	wk_vector_remove(vector,0);
}
extern void wk_vector_pop_back(WVector* vector){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return;
	}
	wk_vector_remove(vector,-1);
}
/**************************************/
/**
 * 链表当前指针操作
 * head可以在没有元素的情况下指向第一个位置
 */
extern void wk_vector_head(WVector* vector){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return;
	}
	if(vector->data!=NULL){
		vector->current=vector->data;
	}else{
		vector->current=NULL;
	}
}

/**
 * 假如0下标没有数据，返回null
 */
extern void wk_vector_begin(WVector* vector){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return;
	}
	if(vector->data!=NULL){
		if(vector->count>0){
			vector->current=vector->data;
		}else{
			vector->current=NULL;
		}
	}else{
		vector->current=NULL;
	}
}

/*
 * 指向vector最后一个元素
 */
extern void wk_vector_end(WVector* vector){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return;
	}
	if(vector->data!=NULL){
		if(vector->count>0){
			vector->current=vector->data+vector->count-1;
		}else{
			vector->current=NULL;
		}
	}else{
		vector->current=NULL;
	}
}

extern void wk_vector_at(WVector* vector,int index){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return;
	}
	/**
	 * 处理负数index
	 */
	index=wk_vector_index(vector,index);
	/*指向的index必须存在元素，负责指向最后一个元素*/
	if(vector->count>0){
		if(index>vector->count-1){
			index=vector->count-1;
		}
	}else{
		vector->current=NULL;
		return;
	}

	if(vector->data!=NULL){
		vector->current=vector->data+index;
	}else{
		vector->current=NULL;
	}
}
extern void wk_vector_next(WVector* vector){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return;
	}
	if(vector->data!=NULL){
		if(vector->current - vector->data >= vector->count-1){
			return;
		}
		vector->current++;
	}
}
extern void wk_vector_prev(WVector* vector){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return;
	}
	if(vector->data!=NULL){
		if(vector->current - vector->data <= 0){
			return;
		}
		vector->current--;
	}
}
extern int wk_vector_hasNext(WVector* vector){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return -1;
	}
	if(vector->data!=NULL){
		if(vector->current - vector->data >= vector->count-1){
			return 0;
		}else{
			return 1;
		}
	}

	return 0;
}
/*******************************/
/**
 * 遍历元素相关
 * ctx上下文
 */
extern void* wk_vector_iterate(WVector* vector,wk_element_iterate_do iterate_do,void* ctx){
	/**
	 * 参数检查
	 */
	if(vector==NULL){
		return NULL;
	}
	void* retp=NULL;
	wk_vector_begin(vector);
	while(wk_vector_hasNext(vector)){
		retp=iterate_do(*vector->current,ctx);
		wk_vector_next(vector);
	}

	return retp;
}
/****************************************************/
/**
 * wk_slist调试函数
 */
extern void wk_vector_debug(){

}
/*****************************************************/
